﻿#define _CRT_SECURE_NO_WARNINGS 1
//#include <iostream>
//using namespace std;
//
//template<class T>
//class SmartPtr
//{
//public:
//	// RAII
//	SmartPtr(T* ptr)
//		:_ptr(ptr)
//	{ }
//
//	~SmartPtr()
//	{
//		cout << "delete[]" << _ptr << endl;
//		delete[] _ptr;
//	}
//
//	// 重载运算符，模拟指针的⾏为，⽅便访问资源
//	T& operator*()
//	{
//		return *_ptr;
//	}
//
//	T* operator->()
//	{
//		return _ptr;
//	}
//
//	T& operator[](size_t i)
//	{
//		return _ptr[i];
//	}
//private:
//	T* _ptr;
//};
//double Divide(int a, int b)
//{
//	// 当b == 0时抛出异常
//	if (b == 0)
//	{
//		throw "Divide by zero condition!";
//	}
//	else
//	{
//		return (double)a / (double)b;
//	}
//}
//void Func()
//{
//	
//	SmartPtr<int> sp1(new int[10]);
//	SmartPtr<int> sp2(new int[10]);
//
//	for (size_t i = 0; i < 10; i++)
//	{
//		sp1[i] = sp2[i] = i;
//	}
//
//	int len, time;
//	cin >> len >> time;
//	cout << Divide(len, time) << endl;
//	
//}
//int main()
//{
//	try
//	{
//		Func();
//	}
//	catch (const char* errmsg)
//	{
//		cout << errmsg << endl;
//	}
//	catch (const exception& e)
//	{
//		cout << e.what() << endl;
//	}
//	catch (...)
//	{
//		cout << "未知异常" << endl;
//	}
//	return 0;
//}

//#include <iostream>
//#include <memory>
//using namespace std;
//
//struct Date
//{
//	int _year;
//	int _month;
//	int _day;
//	Date(int year = 1, int month = 1, int day = 1)
//		:_year(year)
//		, _month(month)
//		, _day(day)
//	{
//	}
//	~Date()
//	{
//		cout << "~Date()" << endl;
//	}
//};
//int main()
//{
//	auto_ptr<Date> ap1(new Date(2025,6,7));
//	// 拷贝时，管理权限转移，被拷⻉对象ap1悬空
//	auto_ptr<Date> ap2(ap1);
//	//空指针访问，ap1对象已经被清空
//	//ap1->_year++;
//
//
//	unique_ptr<Date> up1(new Date(2025, 6, 7));
//	//不支持普通指针隐式类型转换为智能指针对象
//	//unique_ptr<Date> up1=new Date(2025, 6, 7);
//
//	//不支持拷贝构造
//	//unique_ptr<Date> up2(up1);
//	//支持移动构造，up1也被悬空
//	unique_ptr<Date> up3(move(up1));
//	//get()获取底层指针
//	cout << up1.get() << endl;
//	//release()将内存空间释放
//	up3.release();
//	//if(up1.operator bool())
//	if (up1)
//	{
//		cout << "up1 为空" << endl;
//	}
//	else
//	{
//		cout << "up1 不为空" << endl;
//	}
//
//	shared_ptr<Date> sp1(new Date(2025, 6, 7));
//	//不支持普通指针隐式类型转换为智能指针对象
//	//shared_ptr<Date> sp1=new Date(2025, 6, 7)
//	//支持拷贝
//	shared_ptr<Date> sp2(sp1);
//	//支持移动，sp1也会被悬空
//	shared_ptr<Date> sp3(move(sp1));
//	cout << sp2 << endl;
//	cout << sp1 << endl;
//	//use_count()返回引用次数
//	cout << sp2.use_count() << endl;
//	//mask_shared()支持用初始化资源对象的值直接构造
//	shared_ptr<Date> sp4 = make_shared<Date>(2025, 6, 7);
//	auto sp5 = make_shared<Date>(2025, 6, 7);
//
//	return 0;
//}

//#include <iostream>
//#include "shared_ptr.h"
//using namespace std;
//
//struct Date
//{
//	int _year;
//	int _month;
//	int _day;
//	Date(int year = 1, int month = 1, int day = 1)
//		:_year(year)
//		, _month(month)
//		, _day(day)
//	{
//	}
//	~Date()
//	{
//		cout << "~Date()" << endl;
//	}
//};
//
//int main()
//{
//	lh::shared_ptr<Date> sp1(new Date(2025, 6, 7));
//	lh::shared_ptr<Date> sp2(sp1);
//	lh::shared_ptr<Date> sp3(new Date(2025, 6, 7));
//	sp1 = sp3;
//
//	return 0;
//}

//#include <iostream>
//#include <memory>
//using namespace std;
//
//struct Date
//{
//	int _year;
//	int _month;
//	int _day;
//	Date(int year = 1, int month = 1, int day = 1)
//		:_year(year)
//		, _month(month)
//		, _day(day)
//	{
//	}
//	~Date()
//	{
//		cout << "~Date()" << endl;
//	}
//};
//
//class Fclose
//{
//public:
//	void operator()(FILE* ptr)
//	{
//		cout << "fclose:" << ptr << endl;
//		fclose(ptr);
//	}
//};
//
////定制删除器
////定制删除方式，最好使用shared_ptr,最好使用lambda做删除器
//int main()
//{
//	//程序崩溃
//	//shared_ptr<Date> sp1(new Date[10]);
//	//unique_ptr<Date> up1(new Date[10]);
//
//	// 解决⽅案1
//    // 因为new[]经常使⽤，所以unique_ptr和shared_ptr
//    // 实现了⼀个特化版本，这个特化版本析构时⽤的delete[]
//	shared_ptr<Date[]> sp1(new Date[10]);
//	unique_ptr<Date[]> up1(new Date[10]);
//
//
//
//	// 实现其他资源管理的删除器
//	// 仿函数做删除器
//	shared_ptr<FILE> sp5(fopen("test06_07_.cpp", "r"), Fclose());
//	// lambda表达式做删除器
//	shared_ptr<FILE> sp6(fopen("test06_07_.cpp", "r"), [](FILE* ptr) {
//		cout << "fclose:" << ptr << endl;
//		fclose(ptr);
//	});
//
//	// 仿函数做删除器
//	unique_ptr<FILE,Fclose> up5(fopen("test06_07_.cpp", "r"), Fclose());
//	// lambda表达式做删除器
//	auto FcloseFunc = [](FILE* ptr) {
//		cout << "fclose:" << ptr << endl;
//		fclose(ptr);
//		};
//	unique_ptr<FILE, decltype(FcloseFunc)> up6(fopen("test06_07_.cpp", "r"), FcloseFunc);
//
//
//	return 0;
//}

#include <iostream>
#include <memory>
using namespace std;

struct ListNode
{
	int _data;
	//循环引用，造成内存泄露
	//std::shared_ptr<ListNode> _next;
	//std::shared_ptr<ListNode> _prev;

	// 这⾥改成weak_ptr，当n1->_next = n2;绑定shared_ptr时
	// 不增加n2的引⽤计数，不参与资源释放的管理，就不会形成循环引⽤了
	std::weak_ptr<ListNode> _next;
	std::weak_ptr<ListNode> _prev;
	~ListNode()
	{
		cout << "~ListNode()" << endl;
	}
};

int main()
{
	// 循环引⽤ -- 内存泄露
	std::shared_ptr<ListNode> n1(new ListNode);
	std::shared_ptr<ListNode> n2(new ListNode);
	cout << n1.use_count() << endl;
	cout << n2.use_count() << endl;

	n1->_next = n2;
	n2->_prev = n1;

	cout << n1.use_count() << endl;
	cout << n2.use_count() << endl;
	// weak_ptr不⽀持管理资源，不⽀持RAII
	// weak_ptr是专⻔绑定shared_ptr，不增加他的引⽤计数，
	// 作为⼀些场景的辅助管理
	//std::weak_ptr<ListNode> wp(new ListNode);
	return 0;
}
